# import gzip
# from collections import defaultdict
#
# from scapy.all import rdpcap, Raw
# from scapy.layers.inet import IP, TCP
# from xbase_util.packet_util import filter_visible_chars
#
# from package.packet_util import store_tcp_segment, RESPONSE_LINE_RE, HttpParserForDirection, REQUEST_LINE_RE
#
#
# def get_all_packets_by_ack(pkts):
#     sessions = defaultdict(lambda: {
#         'client_ip': None,
#         'server_ip': None,
#         'c2s': {
#             'segments': {},
#             'next_seq': None,
#             'reassembled': b'',
#             'requests': [],
#             'time': [],
#         },
#         's2c': {
#             'segments': {},
#             'next_seq': None,
#             'reassembled': b'',
#             'responses': [],
#             'time': [],
#         }
#     })
#     for pkt in pkts:
#         if not (IP in pkt and TCP in pkt):
#             continue
#         if not pkt.haslayer(Raw):
#             continue
#         time = pkt[IP].time
#         ip_src = pkt[IP].src
#         ip_dst = pkt[IP].dst
#         seq = pkt[TCP].seq
#         payload = bytes(pkt[Raw].load)
#         a = (ip_src, pkt[TCP].sport)
#         b = (ip_dst, pkt[TCP].dport)
#         sd = sessions[(a, b) if a < b else (b, a)]
#         if sd['client_ip'] is None or sd['server_ip'] is None:
#             if REQUEST_LINE_RE.match(payload.lstrip()):
#                 sd['client_ip'] = ip_src
#                 sd['server_ip'] = ip_dst
#             elif RESPONSE_LINE_RE.match(payload.lstrip()):
#                 sd['client_ip'] = ip_dst
#                 sd['server_ip'] = ip_src
#         store_tcp_segment(sd['c2s'] if ip_src == sd['client_ip'] else sd['s2c'], seq, payload, time)
#     for k, sd in sessions.items():
#         cs_http_parser = HttpParserForDirection(is_request=True)
#         cs_http_parser.feed(sd['c2s']['reassembled'])
#         sc_http_parser = HttpParserForDirection(is_request=False)
#         sc_http_parser.feed(sd['s2c']['reassembled'])
#         sd['c2s']['requests'] = cs_http_parser.messages
#         sd['s2c']['responses'] = sc_http_parser.messages
#     packet_list = []
#     for (_, _), sd in sessions.items():
#         c2s = sd['c2s']
#         s2c = sd['s2c']
#         reqs = c2s['requests']
#         resps = s2c['responses']
#         if not reqs and not resps:
#             continue
#         for i, req_data in enumerate(reqs):
#             my_map = {
#                 'req_time': c2s['time'],
#                 'res_time': s2c['time']
#             }
#             req_head_str, req_raw_body, _ = extract_headers_and_body(resps[i])
#             my_map['req_header'] = req_head_str
#             my_map['req_body'] = filter_visible_chars(req_raw_body)
#             my_map['req_len'] = len(req_raw_body)
#             if i < len(resps):
#                 res_head_str, res_raw_body, res_header_dict = extract_headers_and_body(resps[i])
#                 my_map['res_len'] = len(res_raw_body)
#                 my_map['res_header'] = res_head_str
#                 if res_head_str is None:
#                     body = filter_visible_chars(res_raw_body)
#                 else:
#                     print(res_head_str)
#                     if 'gzip' in res_header_dict.get('content-encoding', '').lower():
#                         try:
#                             body = gzip.decompress(res_raw_body).decode("utf-8", errors="replace")
#                         except Exception as e:
#                             print(f"[解压失败] {e}")
#                             print("[DEBUG] raw_body[:80] hex=", res_raw_body[:80].hex())
#                             body = filter_visible_chars(res_raw_body)
#                     else:
#                         body = filter_visible_chars(res_raw_body)
#             else:
#                 print("RESPONSE NOT FOUND.")
#                 body = ""
#             print(body)
#             my_map['res_body'] = body
#             packet_list.append(my_map)
#     return packet_list
#
#
# def extract_headers_and_body(msg_bytes: bytes):
#     header_end = msg_bytes.find(b"\r\n\r\n")
#     if header_end == -1:
#         return None, None, {}
#     header_section = msg_bytes[:header_end]
#     body_bytes = msg_bytes[header_end + 4:]
#     header_str = header_section.decode("utf-8", errors="replace")
#     lines = header_str.split("\r\n")
#     header_dict = {}
#     for l in lines[1:]:
#         if ":" in l:
#             k, v = l.split(":", 1)
#             header_dict[k.strip().lower()] = v.strip()
#     return header_str, body_bytes, header_dict
#
#
# if __name__ == "__main__":
#     packets = get_all_packets_by_ack(rdpcap("../out/err4.pcap"))
#     print(packets)